package org.example.builder;

import org.apache.commons.lang3.ArrayUtils;
import org.example.bean.Constants;
import org.example.bean.FiledInfo;
import org.example.bean.TableInfo;
import org.example.utils.DateUtils;
import org.example.utils.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.*;
import java.util.List;
import java.util.Map;

public class BuildMapper {
    private static Logger logger = LoggerFactory.getLogger(BuildMapper.class);
    public static void execute(TableInfo tableInfo)  {
        File folder = new File(Constants.PATH_MAPPER);

        if(!folder.exists()) {
            folder.mkdirs();
        }

        String className = tableInfo.getBeanName() + Constants.SUFFIX_MAPPER;
        File poFlie = new File(folder,className+ ".java ");
        OutputStream out = null;
        OutputStreamWriter outw = null;
        BufferedWriter bw = null;
        try {

            out = new FileOutputStream(poFlie);
            outw = new OutputStreamWriter(out,"utf8");
            bw = new BufferedWriter(outw);
            bw.write("package " + Constants.PACKAGE_MAPPER + ";");
            bw.newLine();
            bw.newLine();


            bw.write("import org.apache.ibatis.annotations.Param;");
            bw.newLine();
            bw.newLine();
            // 类上加注释
            BuildComment.createClassComment(bw,tableInfo.getComment()+"Mapper");

            bw.write("public interface " + className+"<T, P> extends BaseMapper {");
            bw.newLine();
            bw.newLine();

            //拿到唯一索引
            Map<String, List<FiledInfo>> keyIndexMap = tableInfo.getKeyIndexMap();
            for ( Map.Entry<String, List<FiledInfo>> entry: keyIndexMap.entrySet()) {

                List<FiledInfo> keyFieldIndexList = entry.getValue();
                Integer index = 0;
                StringBuilder methodName = new StringBuilder();
                StringBuilder methodParams = new StringBuilder();
                for (FiledInfo filedInfo: keyFieldIndexList) {
                    index++;
                    methodName.append(StringUtils.upperCaseFirstLetter(filedInfo.getPropertyName()));
                    if(index < keyFieldIndexList.size()) {
                        methodName.append("And");
                    }
                    methodParams.append("@Param(\"" +filedInfo.getPropertyName()+"\") " + filedInfo.getJavaType() + " " + filedInfo.getPropertyName() );
                    if (index < keyFieldIndexList.size()) {
                        methodParams.append(", ");
                    }
                }
                //查询
                BuildComment.createFieldComment(bw,"根据" + methodName+"查询");
                bw.write("\tT selectBy" + methodName + "("+methodParams+");");
                bw.newLine();
                bw.newLine();

                //更新
                BuildComment.createFieldComment(bw,"根据" + methodName+"更新");
                bw.write("\tInteger updateBy" + methodName + "(@Param(\"bean\") T t, "+methodParams+");");
                bw.newLine();
                bw.newLine();
                //删除
                BuildComment.createFieldComment(bw,"根据" + methodName+"删除");
                bw.write("\tInteger deleteBy" + methodName +"("+methodParams+");");
                bw.newLine();
                bw.newLine();

            }


            bw.write("}");
            bw.flush();
        } catch (Exception e) {

            logger.error("创建mapper失败！",e);
        } finally {
            if(bw != null) {
                try {
                    bw.close();
                } catch (IOException e) {
                    throw new RuntimeException(e);
                }
            }
            if(outw != null) {
                try {
                    outw.close();
                } catch (IOException e) {
                    throw new RuntimeException(e);
                }
            }
            if(out != null) {
                try {
                    out.close();
                } catch (IOException e) {
                    throw new RuntimeException(e);
                }
            }

        }
    }

}
